package org.codert.jpa.domain;

import org.springframework.data.domain.Persistable;
import org.springframework.data.util.ProxyUtils;
import org.springframework.lang.Nullable;

import javax.persistence.*;
import java.io.Serializable;

/**
 * @author: TanJingyu
 * @create: 2021-08-19 17:06
 **/
@MappedSuperclass
public abstract class AbstractPersistable<PK extends Serializable> implements Persistable<PK> {
    private static final long serialVersionUID = -5554308939380869754L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Nullable
    private PK id;

    public AbstractPersistable() {
    }

    @Override
    @Nullable
    public PK getId() {
        return this.id;
    }

    protected void setId(@Nullable PK id) {
        this.id = id;
    }

    @Override
    @Transient
    public boolean isNew() {
        return null == this.getId();
    }

    @Override
    public String toString() {
        return String.format("Entity of type %s with id: %s", this.getClass().getName(), this.getId());
    }

    @Override
    public boolean equals(Object obj) {
        if (null == obj) {
            return false;
        } else if (this == obj) {
            return true;
        } else if (!this.getClass().equals(ProxyUtils.getUserClass(obj))) {
            return false;
        } else {
            AbstractPersistable<?> that = (AbstractPersistable<?>)obj;
            return null != this.getId() && this.getId().equals(that.getId());
        }
    }

    @Override
    public int hashCode() {
        int hashCode = 17;
        return hashCode + (null == this.getId() ? 0 : this.getId().hashCode() * 31);
    }
}
